/**
 * @copyright Copyright (c) 2023 BOEVX Automotive Huizhou Limited, All Rights Reserved.
 * @file      button.h
 * @brief     LiteButton operating module that using reading level methon by gpio in the service layer.
 * @version   Initial revision. Rev 1.0.0
 * @author    BOE SCS R&D
 * @date      2023-03-16
 * ********************************************************************************
 * @par       history (The following format is used to generate help documents.)
 * <table>
 * <tr><th>Version <th>Date    <th>Author      <th>Changes and comments
 * <tr><td>V1.0.0 <td>2023-03-16  <td>WangXutao    <td>Created
 * </table>
 */
#ifndef __LITE_BUTTON_H__
#define __LITE_BUTTON_H__

/**************************************** Includes  ****************************************/
#include <stdint.h>
#include <stddef.h>
#include <stdbool.h>
#include "lite_linkedlist.h"

#ifdef __cplusplus
extern "C"
{
#endif

    /**************************************** Definitions  ****************************************/
    /**
     * @brief     Support button event.
     */
    typedef enum
    {
        eLiteButtonEvent_PressDown = 0x00,
        eLiteButtonEvent_PressUp,
        eLiteButtonEvent_Click,       /* Click. */
        eLiteButtonEvent_DoubleClick, /* Double click. */
        eLiteButtonEvent_MultiClick,  /* Continuous click. */
        eLiteButtonEvent_HoldStart,   /* Triggered once at the beginning of hold. */
        eLiteButtonEvent_Holding,     /* Always triggered during hold. */
        eLiteButtonEvent_HoldStop,    /* Triggered once at the end of hold. */
        eLiteButtonEvent_Max,
        eLiteButtonEvent_None,
    } eLiteButtonEvent;

    /**
     * @brief     The struct of button.
     */
    typedef struct xLiteButton
    {
        uint32_t Ticks;
        uint32_t ID;
        uint8_t Repeat : 4;
        uint8_t Event : 4;
        uint8_t State : 3;
        uint8_t DebounceCount : 3;
        uint8_t ActiveLevel : 1;
        uint8_t ButtonLevel : 1;
        uint32_t HoldTimeout;
        uint8_t (*GetPinState)(uint32_t);
        void (*Callback[eLiteButtonEvent_Max])(uint8_t ID, uint8_t Event);
        xLiteLinkedListNode Node;
    } xLiteButton;

    /**************************************** Interfaces  ****************************************/

    /**
     * @brief     Initialize the button struct.
     * @param     Button   The struct of button.
     * @param     ID       The button id.
     * @param     GetPinState Read the button level of gpio pin.
     * @param     ActiveLevel Pressed pin level.
     * @param     HoldTimeout Holding trigger timeout.0 is default.
     * @return    uint8_t  The result of the operations. 0 means no errors.
     */
    extern uint8_t Lite_Button_Init(xLiteButton *Button, uint32_t ID, uint8_t (*GetPinState)(uint32_t), uint8_t ActiveLevel, uint32_t HoldTimeout);

    /**
     * @brief     Attach the button event callback function.
     * @param     Button   The struct of button.
     * @param     Event    Trigger event type.
     * @param     Callback Callback function of triggered event.
     * @return    uint8_t  The result of the operations. 0 means no errors.
     */
    extern uint8_t Lite_Button_Attach(xLiteButton *Button, eLiteButtonEvent Event, void (*Callback)(uint8_t ID, uint8_t Event));

    /**
     * @brief     Inquire the button event happen.
     * @param     Button   The struct of button.
     * @param     eLiteButtonEvent Current button event.
     * @return    uint8_t  The result of the operations. 0 means no errors.
     */
    extern uint8_t Lite_Button_GetEvent(xLiteButton *Button, eLiteButtonEvent *Event);

    /**
     * @brief     Start the button work, add the button into work list.
     * @param     Button   The target button strcut.
     * @return    uint8_t  The result of the operations. 0 means no errors.
     */
    extern uint8_t Lite_Button_Start(xLiteButton *Button);

    /**
     * @brief     Stop the button work, remove the button off work list.
     * @param     Button   The target button strcut.
     * @return    uint8_t  The result of the operations. 0 means no errors.
     */
    extern uint8_t Lite_Button_Stop(xLiteButton *Button);

    /**
     * @brief     The tick function.
     */
    extern void Lite_Button_Tick(void);

#ifdef __cplusplus
}
#endif

#endif
